/*
 * #%L
 * java model
 * %%
 * Copyright (C) 2009 - 2011 prefabware.com Stefan Isele
 * %%
 * All Rights Reserved.
 * This program is dual-licensed under the GNU General Public license
 * or a commercial license.
 * You may select to use one or the other of these licenses.
 * To obtain a commercial license please contact Stefan Isele at www.stefan-isele.de
 * Any modifications to this file must keep this entire header intact.
 * Redistribution, except as permitted by the selected license, is prohibited.
 * #L%
 */
package com.prefabware.jmodel.expression;

import java.util.ArrayList;
import java.util.List;

import com.prefabware.commons.CollectionUtil;
import com.prefabware.commons.collection.Gettable;
import com.prefabware.jmodel.JArgument;
import com.prefabware.jmodel.JMethod;
import com.prefabware.jmodel.code.JCodeOptions;

/**
 * a call to a method
 * 
 * @author sisele_job
 * 
 */
public class JMethodInvocation implements JRightHandSideExpression {
	/**
	 * the target of this call, e.g. object this call will act on
	 */
	private JExpression target;

	public JExpression getTarget() {
		return target;
	}

	public List<JArgumentBinding> getBindings() {
		return bindings;
	}

	/**
	 * the method to call
	 */
	private JMethod method;
	
	/**
	 * the declarations of the arguments to use for the call
	 */
	private List<JArgumentBinding> bindings;

	public JMethodInvocation(JExpression target, JMethod method) {
		super();
		this.bindings = new ArrayList<JArgumentBinding>();
		this.method = method;
		this.target = target;
	}

	public JArgumentBinding bind(JArgument argument, JExpression expression){
		JArgumentBinding binding = new JArgumentBinding(argument,expression);
		this.bindings.add(binding);
		return binding;
	}

	public JMethod getMethod() {
		return method;
	}

	@Override
	public String asCode(JCodeOptions options) {
		return String.format("%s.%s(%s)", this.target.asCode(options),
				this.method.getName(), argumentList(options));
	}

	protected String argumentList(final JCodeOptions options) {
		Gettable<String, JArgumentBinding> gettable = new Gettable<String, JArgumentBinding>() {

			@Override
			public String get(JArgumentBinding from) {
				return from.getExpression().asCode(options);
			}
		};
		List<String> list = CollectionUtil.getList(gettable, this.bindings);
		return CollectionUtil.seperatedBy(list, ",");
	}
	@Override
	public String toString() {
		return this.asCode(JCodeOptions.DEFAULT);
	}
}
